package com.irdstudio.basic.sequence.service.util;

import java.util.Arrays;
import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;

import com.irdstudio.basic.sequence.service.PatternDescriptor;

/**
 * @description:解析PatternDescriptor和组装pattern序列号相关的工具类
 * @date:2019年2月13日 下午5:21:08
 * @author:hengyh
 */
public class PatternDescriptorHelper {
    private static final Map<Integer, String> zerosCache = new ConcurrentHashMap<>(16);

    private static final Map<Integer, Long> maxValueCache = new ConcurrentHashMap<>(16);

    /**
     * @description:将解析后的PatternDescriptor与唯一的uid组合起来
     */
    public static String getSeqFromPatternAndUid(PatternDescriptor descriptor, String uid) {
        String resolvedString = descriptor.getResolvedPatternString();
        String seqName = descriptor.getSeqName();
        return  resolvedString.replace(seqName,
                	padZeroIfNecessary(uid, descriptor.getSeqLength()));
    }
    
    /**
     * @description:在uid前面补0（如果必要）
     */
    public static String padZeroIfNecessary(String uid, Integer seqLength) {
        if (seqLength != null && uid.length() < seqLength) {
        	int diff = seqLength - uid.length();
            String cached = zerosCache.get(diff);
            if (cached == null) {
                final char ZERO = '0';
                char[] characters = new char[diff];
                Arrays.fill(characters, ZERO);
                zerosCache.putIfAbsent(diff, new String(characters));
                cached = zerosCache.get(diff);
            }
            return cached + uid;
        }
        return uid;
    }

    /**
     * @description:从最大序列号长度推算出序列号最大值
     */
    public static Long getMaxValueFromSeqLength(Integer seqLength) {
    	if (seqLength == null) {
			return null;
		}
        Long cached = maxValueCache.get(seqLength);
        if (cached == null) {
            final Character MAXVALUE = '9';
            StringBuilder sb = new StringBuilder();
            for (int i = 0; i < seqLength; i++) {
                sb.append(MAXVALUE);
            }
            maxValueCache.putIfAbsent(seqLength, Long.valueOf(sb.toString()));
            cached = maxValueCache.get(seqLength);
        }
        return cached;
    }
}
